<!--Copyright to Shen Huang, you can reach me out at shenhuang@live.ca-->

<!DOCTYPE html>
<meta name = "viewport" content = "width = device-width, initial-scale = 1.0">
<html>
	<head>
		<title>BUBBLE DEMO</title>
		<style>
		body	{
			background-color : #a3d2ff;
		}
		html, body {
			max-width: 100%;
			overflow-x: hidden;
			overflow-y: hidden;
		}
		.bubble {
			z-index : 999;
			position : absolute;
			border-radius : 50%;
		}
		sand {
			z-index : 0;
			position : absolute;
			top : 60%;
			left : -10%;
			width: 110%;
			border-bottom : 300px solid #ffedc6;
			border-left : 100px solid transparent;
		}
		water {
			z-index : 1;
			position : absolute;
			top : 45%;
			left : -30%;
			height : 60%;
			width : 100%;
			background-color : #84abff;
			border-radius : 50%;
		}
		skymask {
			z-index : 2;
			position : absolute;
			top : 30%;
			left : -10%;
			height : 30%;
			width : 80%;
			background-color : #a3d2ff;
		}
		boat {
			z-index : 3;
			position : absolute;
			top : 90%;
			left : 20%;
			width: 70px;
			border-top : 10px solid #ffd6f9;
			border-left : 5px solid transparent;
			border-right : 5px solid transparent;
		}
		mast {
			z-index : 4;
			position : absolute;
			top : -70px;
			left : 50px;
			height : 60px;
			width : 5px;
			background-color : #efeded;
		}
		sail {
			z-index : 3;
			position : absolute;
			top : -70px;
			left : 10px;
			width : 5px;
			border-bottom : 50px solid #ffffff;
			border-left : 40px solid transparent;
		}
		tree {
			z-index : 2;
			position : absolute;
			top : 55%;
			left : 80%;
		}
		branch {
			z-index : 2;
			position : absolute;
			top : 0px;
			left : 0px;
			height : 90px;
			width : 40px;
			border : 1px;
			border-color : #7f6048;
			border-style : solid;
			background-color : #bc8e6b;
			border-radius : 50%;
			-webkit-clip-path : polygon(20px -30px, 70px 0px, 35px 80px, 10px 80px, 30px 55px);
			clip-path : polygon(20px -30px, 70px 0px, 35px 80px, 10px 80px, 30px 55px);
		}
		leaf1 {
			z-index : 2;
			position : absolute;
			top : -5px;
			left : -55px;
			height : 15px;
			width : 70px;
			border : 1px;
			border-color : #527c51;
			border-style : solid;
			background-color : #6fad6b;
			border-radius : 50%;
			-webkit-clip-path : ellipse(40px 25px at 60px 30px);
			clip-path : ellipse(40px 25px at 60px 30px);
			transform : scaleX(1.2) rotate(0deg);
		}
		leaf2 {
			z-index : 2;
			position : absolute;
			top : -15px;
			left : -35px;
			height : 15px;
			width : 70px;
			border : 1px;
			border-color : #527c51;
			border-style : solid;
			background-color : #6fad6b;
			border-radius : 50%;
			-webkit-clip-path : ellipse(40px 15px at 60px 20px);
			clip-path : ellipse(40px 15px at 60px 20px);
			transform : scaleX(0.7) rotate(15deg);
		}
		leaf3 {
			z-index : 2;
			position : absolute;
			top : 5px;
			left : -35px;
			height : 15px;
			width : 70px;
			border : 1px;
			border-color : #527c51;
			border-style : solid;
			background-color : #6fad6b;
			border-radius : 50%;
			-webkit-clip-path : ellipse(40px 15px at 60px 20px);
			clip-path : ellipse(40px 15px at 60px 20px);
			transform : scaleX(0.7) rotate(-10deg);
		}
		leaf4 {
			z-index : 2;
			position : absolute;
			top : -7px;
			left : 30px;
			height : 15px;
			width : 70px;
			border : 1px;
			border-color : #527c51;
			border-style : solid;
			background-color : #6fad6b;
			border-radius : 50%;
			-webkit-clip-path : ellipse(40px 25px at 60px 30px);
			clip-path : ellipse(40px 25px at 60px 30px);
			transform : scaleX(-1.2) rotate(0deg);
		}
		leaf5 {
			z-index : 2;
			position : absolute;
			top : -20px;
			left : 10px;
			height : 15px;
			width : 70px;
			border : 1px;
			border-color : #527c51;
			border-style : solid;
			background-color : #6fad6b;
			border-radius : 50%;
			-webkit-clip-path : ellipse(40px 15px at 60px 20px);
			clip-path : ellipse(40px 15px at 60px 20px);
			transform : scaleX(-0.7) rotate(20deg);
		}
		leaf6 {
			z-index : 2;
			position : absolute;
			top : 5px;
			left : 15px;
			height : 15px;
			width : 70px;
			border : 1px;
			border-color : #527c51;
			border-style : solid;
			background-color : #6fad6b;
			border-radius : 50%;
			-webkit-clip-path : ellipse(40px 15px at 60px 20px);
			clip-path : ellipse(40px 15px at 60px 20px);
			transform : scaleX(-0.7) rotate(-10deg);
		}
		coconut1 {
			z-index : 3;
			position : absolute;
			top : 1px;
			left : 10px;
			height : 15px;
			width : 15px;
			border : 1px;
			border-color : #827d5d;
			border-style : solid;
			background-color : #a59f78;
			border-radius : 50%;
		}
		coconut2 {
			z-index : 3;
			position : absolute;
			top : -1px;
			left : 21px;
			height : 15px;
			width : 15px;
			border : 1px;
			border-color : #827d5d;
			border-style : solid;
			background-color : #a59f78;
			border-radius : 50%;
		}
		coconut3 {
			z-index : 3;
			position : absolute;
			top : 5px;
			left : 15px;
			height : 15px;
			width : 15px;
			border : 1px;
			border-color : #827d5d;
			border-style : solid;
			background-color : #a59f78;
			border-radius : 50%;
		}
		</style>
	</head>
	<body>
		<div id = "board"></div>
		<sand></sand>
		<water></water>
		<skymask></skymask>
		<boat>
			<mast></mast>
			<sail></sail>
		</boat>
		<tree>
			<branch></branch>
			<leaf1></leaf1>
			<leaf2></leaf2>
			<leaf3></leaf3>
			<leaf4></leaf4>
			<leaf5></leaf5>
			<leaf6></leaf6>
			<coconut1></coconut1>
			<coconut2></coconut2>
			<coconut3></coconut3>
		</tree>
	</body>
	<script>

		var brd = document.createElement("DIV");
		document.body.insertBefore(brd, document.getElementById("board"));

		bubbles = [];

		const d = 5000;
		const o = 0.7;
		const r = 0.001;
		const f = 0.0025;
		const p = 0.00000001;
		const minbub = 10;
		const maxbub = 50;
		const cursorXOffset = 5;
		const cursorYOffset = 0;

		function newBubble(x, y, size, color)
		{
			var bubble = document.createElement("DIV");
			bubble.setAttribute('class', 'bubble');
			bubble.style = "background-color : " + color + ";";
			bubble.bubbleSize = size;
			bubble.style.height = bubble.bubbleSize * 2 + "px";
			bubble.style.width = bubble.bubbleSize * 2 + "px";
			bubble.time = d;
			bubble.velocity = [];
			bubble.velocity.x = 0;
			bubble.velocity.y = 0;
			bubble.position = [];
			bubble.position.x = x;
			bubble.position.y = y;
			bubble.style.left = bubble.position.x - bubble.bubbleSize + 'px';
			bubble.style.top = bubble.position.y - bubble.bubbleSize + 'px';				
			brd.appendChild(bubble);
			if(bubbles == null)
				bubbles = [];
			bubbles.push(bubble);
			return bubble;
		}

		var msedwn = false;

		document.onmousedown = function(e) {
			msedwn = true;
		}

		document.onmouseup = function(e) {
			msedwn = false;
		}

		document.onmousemove = function(e) {
			if(msedwn)
				generateBubbles(e.pageX - brd.offsetLeft + cursorXOffset, e.pageY - brd.offsetTop + cursorYOffset);
		}

		document.ontouchmove = function(e) {
			generateBubbles(e.touches[0].pageX, e.touches[0].pageY);
		}

		function generateBubbles(x, y)
		{
			var size = minbub + (maxbub - minbub) * Math.random();
			var digits = '0123456789ABCDEF';
			var color = '#';
			for (var i = 0; i < 6; i++) {
				color += digits[Math.floor(Math.random() * 16)];
			}
			newBubble(x, y, size, color);
		}

		function bubblePushAround(deltaTime)
		{
			for(i = 0; i < bubbles.length; i++)
			{
				for(j = i + 1; j < bubbles.length; j++)
				{
					var bubbleOne = bubbles[i];
					var bubbleTwo = bubbles[j];
					var Dx = bubbleOne.position.x - bubbleTwo.position.x;
					var Dy = bubbleOne.position.y - bubbleTwo.position.y;
					var D2 = Dx * Dx + Dy * Dy;
					var R12 = bubbleOne.bubbleSize * bubbleOne.bubbleSize;
					var R22 = bubbleTwo.bubbleSize * bubbleTwo.bubbleSize;
					if(D2 < R12 + R22)
					{
						var D = Math.sqrt(D2);
						var F1 = (D2 - (R12 + R22)) * R22;
						var F2 = (D2 - (R12 + R22)) * R12;
						bubbleOne.velocity.x -= F1 * p * Dx / D * deltaTime;
						bubbleOne.velocity.y += F1 * p * Dy / D * deltaTime;
						bubbleTwo.velocity.x += F2 * p * Dx / D * deltaTime;
						bubbleTwo.velocity.y -= F2 * p * Dy / D * deltaTime;
					}
				}
			}
		}

		var before = Date.now();
		var id = setInterval(frame, 5);
		
		function frame()
		{
			var current = Date.now();
			var deltaTime = current - before;
			before = current;
			bubblePushAround(deltaTime);
			for(i in bubbles)
			{
				var bubble = bubbles[i];
				bubble.time -= deltaTime;
				if(bubble.time > 0)
				{
					bubble.velocity.y += f * deltaTime;
					bubble.velocity.x -= bubble.velocity.x * r * bubble.bubbleSize * deltaTime;
					bubble.velocity.y -= bubble.velocity.y * r * bubble.bubbleSize * deltaTime;
					bubble.position.x += bubble.velocity.x * deltaTime;
					bubble.position.y -= bubble.velocity.y * deltaTime;
					bubble.style.left = bubble.position.x - bubble.bubbleSize + 'px';
					bubble.style.top = bubble.position.y - bubble.bubbleSize + 'px';
					bubble.style.opacity = o * (bubble.time / d);
				}
				else
				{
					bubble.parentNode.removeChild(bubble);
					bubbles.splice(i, 1);
				}
			}
		}

	</script>
</html>